/// <reference path="../_all.ts" />

module Application.Controllers {

    export class UsersController implements Application.Interfaces.Controllers.IController {

        public static $inject = [
            '$rootScope',
            '$scope',
            '$location',
            'UserService',
            'TranslationService',
        ];

        updateResult: {
            (data): void;
            (data, err): void;
        };

        loadResult: {
            (data): void;
            (data, err): void;
        };

        constructor(public RootScope: Application.Interfaces.Scopes.IRootScope
            , public Scope: Application.Interfaces.Scopes.IUsersScope
            , public Location: ng.ILocationService
            , public Users: Application.Interfaces.Services.IUserService
            , public Translations: Application.Interfaces.Services.ITranslationService) {
            this.Scope.vm = this;
            this.Scope.user = this.RootScope.user;
            this.Scope.location = this.Location;
            this.Scope.messages = new Application.Utility.Messages();
            this.Scope.navigations = new Application.Utility.Navigations();
            this.Scope.users = <Application.Resources.IUser[]>[];
            this.Scope.selecteduser = <Application.Resources.IUser>{};

                this.Scope.navigations.AddLink(Translations.Translate("SERVERLIST"), "/servers", false, false, Application.Constants.Icons.Servers);
                this.Scope.navigations.AddLink(Translations.Translate("ACTIONS"), "/actions", false, false, Application.Constants.Icons.Actions);
            if (this.Scope.user && this.Scope.user.role && this.Scope.user.role >= 2) {
                this.Scope.navigations.AddLink(Translations.Translate("PLAYERS"), "/players", false, false, Application.Constants.Icons.Bans);
            };
            if (this.Scope.user && this.Scope.user.role && this.Scope.user.role >= 8) {
                this.Scope.navigations.AddLink(Translations.Translate("USERS"), "/users", true, false, Application.Constants.Icons.Users);
            };
                this.Scope.navigations.AddLinkRight(Translations.Translate("ACCOUNT"), "/users/" + this.Scope.user.user_id, false);
                this.Scope.navigations.AddLinkRight(Translations.Translate("LOGOUT"), "/", false);

            if (this.Scope.user && this.Scope.user.role && this.Scope.user.role > 4) {
                this.updateResult = (data, err?) => {
                    this.updateResultProxy.apply(this, [data, err]);
                };

                this.loadResult = (data, err?) => {
                    this.loadResultProxy.apply(this, [data, err]);
                };

                this.load();
            };
        }

        public log(msg: string) {
            //console.log(msg);
        }

        public load() {
            this.log('load');
            this.Users.GetUsers(this.loadResult);
        }

        private loadResultProxy(data, err) {
            this.log('load result');
            if (data != null) {
                var users = <Application.Resources.IUser[]> data;
                if (users != null && users.length > 0) {
                    this.Scope.messages.AddAndGrowl(Application.Utility.MessageType.info, "Info", new Application.Utility.String(this.Translations.Translate('FOUNDUSERS')).format(users.length.toString()));
                    var result: Application.Resources.IUser;
                    for (var i = 0; i < this.Scope.users.length; i++) {
                        result = null;
                        for (var j = 0; j < users.length; j++) {
                            if (this.Scope.users[i].user_id == users[j].user_id) {
                                result = users[j];
                                Application.Resources.UserUtility.fixBooleans(result);
                                users.splice(j, 1);
                                break;
                            };
                        };
                        if (result == null) {
                            this.Scope.users.splice(i, 1);
                            i--;
                        } else {
                            this.Scope.users[i] = result;
                        };
                    };
                    for (var i = 0; i < users.length; i++) {
                        result = users[i];
                        Application.Resources.UserUtility.fixBooleans(result);
                        this.Scope.users.push(result);
                    };
                } else {
                    this.Scope.messages.AddAndGrowl(Application.Utility.MessageType.error, "Error", this.Translations.Translate('USERSNOTFOUND'));
                };
            } else {
                if (err != null) {
                    this.Scope.messages.AddAndGrowl(Application.Utility.MessageType.error, err.data.status + ' ' + err.data.type, err.data.message);
                } else {
                    this.Scope.messages.AddAndGrowl(Application.Utility.MessageType.error, '000 Unknown', this.Translations.Translate('UNKNOWNERROR'));
                };
            };
        }

        private fixBooleans(item: Application.Resources.IUser) {
            item.is_active = item.is_active === null ? true : item.is_active;
            item.is_blocked = item.is_blocked === null ? false : item.is_blocked;
        }

        public update(user: Application.Resources.IUser) {
            this.log('update');
            this.Users.PostUser(user, this.updateResult);
        }

        private updateResultProxy(data, err) {
            this.log('update result');
            if (data != null) {
                var user = <Application.Resources.IUser> data;
                if (user != null) {
                    Application.Resources.UserUtility.fixBooleans(user);
                    if (user.password && user.password.length > 0) {
                        this.Scope.messages.AddAndGrowl(Application.Utility.MessageType.success, "Info", new Application.Utility.String(this.Translations.Translate('USERADDEDWITHPASS')).format(user.login, user.password));
                        delete user.password;
                    } else {
                        this.Scope.messages.AddAndGrowl(Application.Utility.MessageType.success, "Info", new Application.Utility.String(this.Translations.Translate('USERUPDATED')).format(user.login));
                    };
                    var arr = <Application.Resources.IUser[]>$.grep(this.Scope.users, function (n: Application.Resources.IUser, i) {
                        return (n.user_id == user.user_id);
                    });
                    if (arr != null && arr.length > 0) {
                        var found = arr[0];
                        found.role = user.role;
                        found.is_active = user.is_active;
                        found.is_blocked = user.is_blocked;
                        if ((<any>found).reset) {
                            delete (<any>found).reset;
                        };
                    } else {
                        this.Scope.users.push(user);
                    };
                } else {
                    this.Scope.messages.AddAndGrowl(Application.Utility.MessageType.error, "Error", this.Translations.Translate('USERNOTFOUND'));
                };
            } else {
                if (err != null) {
                    this.Scope.messages.AddAndGrowl(Application.Utility.MessageType.error, err.data.status + ' ' + err.data.type, err.data.message);
                } else {
                    this.Scope.messages.AddAndGrowl(Application.Utility.MessageType.error, '000 Unknown', this.Translations.Translate('UNKNOWNERROR'));
                };
            };
        }

        public addUser(user: Application.Resources.IUser) {
            var arr = <Application.Resources.IUser[]>$.grep(this.Scope.users, function (n: Application.Resources.IUser, i) {
                return (n.login == user.login);
            });
            if (arr != null && arr.length > 0) {
                this.Scope.messages.AddAndGrowl(Application.Utility.MessageType.error, "Error", this.Translations.Translate('TWOUSERSSAMENAME'));
            } else {
                user.is_active = true;
                user.role = 1;
                user.is_blocked = false;
                this.update(user);
                this.Scope.selecteduser = <Application.Resources.IUser>{};
                $('#new_user_login').val('');
            };
        }

        public disableUser(user_id: number) {
            var arr =<Application.Resources.IUser[]>$.grep(this.Scope.users, function (n: Application.Resources.IUser, i) {
                return (n.user_id == user_id);
            });
            if (arr != null && arr.length > 0) {
                var user = arr[0];
                user.is_active = false;
                this.update(user);
            };
        }

        public enableUser(user_id: number) {
            var arr = <Application.Resources.IUser[]>$.grep(this.Scope.users, function (n: Application.Resources.IUser, i) {
                return (n.user_id == user_id);
            });
            if (arr != null && arr.length > 0) {
                var user = arr[0];
                user.is_active = true;
                user.is_blocked = false;
                this.update(user);
            };
        }

        public resetPassword(user_id: number) {
            var arr = <Application.Resources.IUser[]>$.grep(this.Scope.users, function (n: Application.Resources.IUser, i) {
                return (n.user_id == user_id);
            });
            if (arr != null && arr.length > 0) {
                var user = <any>arr[0];
                user.reset = true;
                this.update(user);
            };
        }

        public increaseRole(user_id: number) {
            var arr = <Application.Resources.IUser[]>$.grep(this.Scope.users, function (n: Application.Resources.IUser, i) {
                return (n.user_id == user_id);
            });
            if (arr != null && arr.length > 0) {
                var user = arr[0];
                if (user.role < 8) {
                    user.role = user.role * 2;
                    this.update(user);
                } else {
                    this.Scope.messages.AddAndGrowl(Application.Utility.MessageType.error, "Error", this.Translations.Translate('NOROLEHIGHER'));
                };
            };
        }

        public decreaseRole(user_id: number) {
            var arr = <Application.Resources.IUser[]>$.grep(this.Scope.users, function (n: Application.Resources.IUser, i) {
                return (n.user_id == user_id);
            });
            if (arr != null && arr.length > 0) {
                var user = arr[0];
                if (user.role > 1) {
                    user.role = user.role / 2;
                    this.update(user);
                } else {
                    this.Scope.messages.AddAndGrowl(Application.Utility.MessageType.error, "Error", this.Translations.Translate('NOROLELOWER'));
                };
            };
        }
    };
}